/**
 * 
 */
package net.sf.tools.uiconfig.tags.config;

import java.io.IOException;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.text.Format;

import javax.servlet.jsp.JspException;

import org.apache.commons.lang.StringUtils;

import net.sf.tools.uiconfig.tags.AbstractViewTag;
import net.sf.tools.uiconfig.text.FormatManager;

/**
 * @author sabuj.das
 *
 */
public class DataOutTag extends AbstractViewTag {

	/**
	 * 
	 */
	private static final long serialVersionUID = 607394601882443610L;
	private Object dataObject;
	private String targetFieldName;
	private String defaultValue = "";
	private boolean formatData = false;
	private String formatString;
	
	
	/**
	 * 
	 */
	public DataOutTag() {
		// TODO Auto-generated constructor stub
	}

	/**
	 * @return the dataObject
	 */
	public Object getDataObject() {
		return dataObject;
	}

	/**
	 * @param dataObject the dataObject to set
	 */
	public void setDataObject(Object dataObject) {
		this.dataObject = dataObject;
	}

	/**
	 * @return the targetFieldName
	 */
	public String getTargetFieldName() {
		return targetFieldName;
	}

	/**
	 * @param targetFieldName the targetFieldName to set
	 */
	public void setTargetFieldName(String targetFieldName) {
		this.targetFieldName = targetFieldName;
	}

	/**
	 * @return the defaultValue
	 */
	public String getDefaultValue() {
		return defaultValue;
	}

	/**
	 * @param defaultValue the defaultValue to set
	 */
	public void setDefaultValue(String defaultValue) {
		this.defaultValue = defaultValue;
	}

	/**
	 * @return the formatData
	 */
	public boolean isFormatData() {
		return formatData;
	}

	/**
	 * @return the formatString
	 */
	public String getFormatString() {
		return formatString;
	}

	/**
	 * @param formatData the formatData to set
	 */
	public void setFormatData(boolean formatData) {
		this.formatData = formatData;
	}

	/**
	 * @param formatString the formatString to set
	 */
	public void setFormatString(String formatString) {
		this.formatString = formatString;
	}

	/* (non-Javadoc)
	 * @see javax.servlet.jsp.tagext.TagSupport#doStartTag()
	 */
	@Override
	public int doStartTag() throws JspException {
		String value = getDefaultValue();
		if(null != getDataObject()
				&& null != getTargetFieldName()
				&& !"".equals(getTargetFieldName().trim())){
			try {
				Method method = getDataObject().getClass().getMethod("get"+StringUtils.capitalize(getTargetFieldName()), null);
				if(null != method){
					value = getStringValue(method.invoke(dataObject, new Object[]{}));
				}
			} catch (SecurityException e) {
				pageContext.getServletContext().log(e.getLocalizedMessage(), e);
			} catch (NoSuchMethodException e) {
				pageContext.getServletContext().log(e.getLocalizedMessage(), e);
			} catch (IllegalArgumentException e) {
				pageContext.getServletContext().log(e.getLocalizedMessage(), e);
			} catch (IllegalAccessException e) {
				pageContext.getServletContext().log(e.getLocalizedMessage(), e);
			} catch (InvocationTargetException e) {
				pageContext.getServletContext().log(e.getLocalizedMessage(), e);
			} catch (Exception e) {
				pageContext.getServletContext().log(e.getLocalizedMessage(), e);
			}
		}
		
		try {
			pageContext.getOut().write(value);
		} catch (IOException e) {
			pageContext.getServletContext().log(e.getLocalizedMessage(), e);
		}
		
		return SKIP_BODY;
	}
	
	private String getStringValue(Object value){
		if(null == value)
			return getDefaultValue();
		
		if(isFormatData()){
			try {
				Format format = FormatManager.getInstance().getDataFormat(value.getClass(), formatString);
				if(null == format){
					pageContext.getServletContext().log("Unsupported format pattern: ", new IllegalArgumentException("Unsupported format pattern: " + getFormatString()));
					return value.toString();
				}
				return format.format(value);
			} catch (Exception e) {
				pageContext.getServletContext().log(e.getLocalizedMessage(), e);
				return value.toString();
			}
		}
		
		return value.toString();
	}
	
}
